﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using OpenQuarters.WebQuarters.Utils;
using System.Data.Linq;

namespace OpenQuarters.WebQuarters.Core
{
    [Serializable]
    public class Ordering
    {
        private string id = null;

        public string Id
        {
            get
            {
                if (id == null)
                {
                    id = Utils.GeneralUtils.GetGuid();
                }
                return id;
            }
            set { id = value; }
        }

        public string Field { get; set; }
        public string Operator { get; set; }
        /// <summary>
        /// This field has been depreciated, but has been maintained for backwards compatibility (as of v1.0.4)
        /// </summary>
        public Type Type { get; set; }

        public string OperatorName
        {
            get
            {
                switch (this.Operator)
                {
                    case "asc":
                        return "ascending";
                    case "desc":
                        return "descending";
                    default:
                        return "asc";
                }
            }
        }

        public string OperatorNameAsString
        {
            get
            {
                return OperatorName;
            }
        }

        public Ordering()
        {
        }

        public Ordering(string field)
        {
            this.Field = field;
        }

        public void Order<T>(List<T> items)
        {
            items.Sort(new Comparison<T>(compare<T>));
        }

        private int compare<T>(T item1, T item2)
        {
            if (item1 == null || item2 == null)
            {
                return 0;
            }
            var prop = item1.GetType().GetProperty(this.Field);
            if (prop == null)
            {
                return 0;
            }
            var obj1Value = prop.GetValue(item1, null);
            var obj2Value = prop.GetValue(item2, null);
            var r = ((IComparable)obj1Value).CompareTo((IComparable)obj2Value);

            switch (this.Operator)
            {
                case "desc":
                    // If -1 return 1, if 0 return 0, if 1 return -1
                    return r == 1 ? -1 : (r == -1 ? 1 : 0);
                default:
                    return r;
            }
        }
    }
}
